﻿using HalconDotNet;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace 多尺度相机采集
{
    class MyHalcon
    {
        public MyHalcon()
        {
            // Default settings used in HDevelop 
            HOperatorSet.SetSystem("width", 512);
            HOperatorSet.SetSystem("height", 512);
            if (HalconAPI.isWindows)
                HOperatorSet.SetSystem("use_window_thread", "true");
        }

        public int DrawROI(HObject ho_Image, HWindowControl hWindowControl, HTuple hv_WindowHandle, out HObject test_Image)
        {
            if (ho_Image == null)
            {
                test_Image = null;
                return 1;
            }

            HOperatorSet.DispObj(ho_Image, hv_WindowHandle);  // 重新显示一下图像是为了消除上次绘制的ROI
            HOperatorSet.SetColor(hv_WindowHandle, "red");
            HOperatorSet.SetDraw(hv_WindowHandle, "margin");
            HOperatorSet.SetLineWidth(hv_WindowHandle, 2);
            HOperatorSet.DrawRectangle1(hv_WindowHandle, out HTuple hv_Row1, out HTuple hv_Column1, out HTuple hv_Row2, out HTuple hv_Column2);
            HOperatorSet.GenRectangle1(out HObject ho_ROI, hv_Row1, hv_Column1, hv_Row2, hv_Column2);
            HOperatorSet.ReduceDomain(ho_Image,  ho_ROI, out HObject ho_Temp);
            HOperatorSet.DispObj(ho_ROI, hv_WindowHandle);
            test_Image = ho_Temp;

            return 0;
        }

        /// <summary>
        /// 计算散斑质量评价指标
        /// </summary>
        /// <param name="ho_Image">输入图像</param>
        /// <param name="mig">平均灰度梯度</param>
        /// <param name="misd">平均灰度 2 阶导数</param>
        /// <param name="histo">灰度直方图数据</param>
        /// <returns></returns>
        public int CalMeanIntensityGradient(HObject ho_Image, out string mig, out string misd, out double[] histo)
        {
            if (ho_Image == null)
            {
                mig = "erro";
                misd = "erro";
                histo = null;
                return 1;
            }

            double temp1, temp2;
            HObject ho_GrayImage, ho_DerivX;
            HObject ho_DerivY, ho_DerivXX, ho_DerivYY, ho_DerivY2, ho_DerivX2;
            HObject ho_DerivX2Y2, ho_SqrtImage1, ho_DerivYY2, ho_DerivXX2;
            HObject ho_DerivXX2YY2, ho_SqrtImage2;
            //HTuple hv_Deviation1 = null, hv_Mean1 = null, hv_Mean2 = null, hv_Deviation2 = null;

            HOperatorSet.GenEmptyObj(out ho_GrayImage);
            HOperatorSet.GenEmptyObj(out ho_DerivX);
            HOperatorSet.GenEmptyObj(out ho_DerivY);
            HOperatorSet.GenEmptyObj(out ho_DerivXX);
            HOperatorSet.GenEmptyObj(out ho_DerivYY);
            HOperatorSet.GenEmptyObj(out ho_DerivY2);
            HOperatorSet.GenEmptyObj(out ho_DerivX2);
            HOperatorSet.GenEmptyObj(out ho_DerivX2Y2);
            HOperatorSet.GenEmptyObj(out ho_SqrtImage1);
            HOperatorSet.GenEmptyObj(out ho_DerivYY2);
            HOperatorSet.GenEmptyObj(out ho_DerivXX2);
            HOperatorSet.GenEmptyObj(out ho_DerivXX2YY2);
            HOperatorSet.GenEmptyObj(out ho_SqrtImage2);

            HOperatorSet.Rgb1ToGray(ho_Image, out ho_GrayImage);
            //求图像xy方向的一阶导数与二阶导数
            ho_DerivX.Dispose();
            HOperatorSet.DerivateGauss(ho_GrayImage, out ho_DerivX, 1, "x");
            ho_DerivY.Dispose();
            HOperatorSet.DerivateGauss(ho_GrayImage, out ho_DerivY, 1, "y");
            ho_DerivXX.Dispose();
            HOperatorSet.DerivateGauss(ho_GrayImage, out ho_DerivXX, 1, "xx");
            ho_DerivYY.Dispose();
            HOperatorSet.DerivateGauss(ho_GrayImage, out ho_DerivYY, 1, "yy");

            //获取一阶与二阶导数平方的和再开方（即灰度梯度矢量模）
            ho_DerivY2.Dispose();
            HOperatorSet.MultImage(ho_DerivY, ho_DerivY, out ho_DerivY2, 1, 0);
            ho_DerivX2.Dispose();
            HOperatorSet.MultImage(ho_DerivX, ho_DerivX, out ho_DerivX2, 1, 0);
            ho_DerivX2Y2.Dispose();
            HOperatorSet.AddImage(ho_DerivX2, ho_DerivY2, out ho_DerivX2Y2, 1, 0);
            ho_SqrtImage1.Dispose();
            HOperatorSet.SqrtImage(ho_DerivX2Y2, out ho_SqrtImage1);
            ho_DerivYY2.Dispose();
            HOperatorSet.MultImage(ho_DerivYY, ho_DerivYY, out ho_DerivYY2, 1, 0);
            ho_DerivXX2.Dispose();
            HOperatorSet.MultImage(ho_DerivXX, ho_DerivXX, out ho_DerivXX2, 1, 0);
            ho_DerivXX2YY2.Dispose();
            HOperatorSet.AddImage(ho_DerivXX2, ho_DerivYY2, out ho_DerivXX2YY2, 1, 0);
            ho_SqrtImage2.Dispose();
            HOperatorSet.SqrtImage(ho_DerivXX2YY2, out ho_SqrtImage2);

            //求灰度梯度矢量模均值
            HOperatorSet.Intensity(ho_SqrtImage1, ho_SqrtImage1, out HTuple hv_Mean1, out HTuple hv_Deviation1);
            HOperatorSet.Intensity(ho_SqrtImage2, ho_SqrtImage2, out HTuple hv_Mean2, out HTuple hv_Deviation2);

            temp1 = hv_Mean1;
            mig = temp1.ToString("0.00");
            temp2 = hv_Mean2;
            misd = temp2.ToString("0.00");

            HOperatorSet.GrayHisto(ho_Image, ho_Image, out HTuple hv_AbsoluteHisto, out HTuple hv_RelativeHisto);
            histo = hv_RelativeHisto;

            return 0;
        }
    }
}
